package flown.window.graphics.ui;


import flown.window.graphics.Scene;
import flown.window.graphics.ui.event.Event;

import java.util.ArrayList;



/**
 * @author flown
 * 一个scene可以有多个容器
 * 容器（Container）有自己在scene中的位置——x,y——与大小——width,height
 * */
public class Container
{
    private final ArrayList<Widget> widget;///< 容器组件列表
    private Scene at = null;///< 容器所在scene
    private int index = 99999;///< 在the common event of the scene中的index
    public int x;///< 在scene中的X
    public int y;///< 在scene中的y
    public int width;///< container的width,the width of the container
    public int height;///< the height of the container

    public Container() { this(0, 0); }
    public Container(int x, int y)
    {
        this(x, y, 0, 0);
    }

    /**
     * 若width或height中有为0者则插入scene后都会被设为scene的width和height
     *
     * @param x 容器x
     * @param y 容器y
     * @param width 容器width
     * @param height 容器height
     */
    public Container(int x, int y, int width, int height)
    {
        this.x = x;
        this.y = y;
        this.width = width;
        this.height = height;
        widget = new ArrayList<>();
    }

    /**
     * 插入到Scene中
     * @param scene scene
     */
    public final void InsertIntoScene(Scene scene) {
        Container that = this;
        this.at = scene;

        //若容器宽或高为0，则宽高设为scene的宽高
        if (this.width == 0 || this.height == 0)
        {
            this.width = scene.getWidth();
            this.height = scene.getHeight();
        }
        this.index = this.at.AddCommonEvent(renderer -> {

            renderer.Translate(this.x, this.y);//设置容器在scene中的位置
            for (Widget widget : that.widget)
            {
                widget.Render(renderer);
                int right = this.x + this.width;
                int bottom = this.y + this.height;
                int widget_right_minus_width = widget.GetX() + widget.GetWidth() - this.width;//用来判断组件的最右边会不会超出容器的宽，值>0则为超出
                int widget_bottom_minus_height = widget.GetY() + widget.GetHeight() - this.height;//用来判断组件的最下边会不会超出容器的高，值>0则为超出
                if (widget_right_minus_width > 0)
                    renderer.GetGraphics2D().clearRect(right, widget.GetY(), widget_right_minus_width, widget.GetHeight());
                if (widget_bottom_minus_height > 0)
                    renderer.GetGraphics2D().clearRect(widget.GetX(), bottom, widget.GetWidth(), widget_bottom_minus_height);

                Event e = new Event(widget,this.at.getMousePosition().getLocation());
                if
                (
                        e.GetLocationMouseX() >= widget.GetX() &&
                        e.GetLocationMouseX() <= right &&
                        e.GetLocationMouseY() >= widget.GetY() &&
                        e.GetLocationMouseY() <= bottom
                )
                    widget.listener_action.click(e);
            }
            renderer.Translate(-this.x, -this.y);
        });
    }
    public final void RemoveFromScene() { if (this.index != 99999) this.at.GetCommonEvent().remove(this.index); }


    public final void SetBounds(int x, int y, int width, int height)
    {
        this.x = x;
        this.y = y;
        this.width = width;
        this.height= height;
    }
    public final ArrayList<Widget> GetWidgets() { return this.widget; }
    public final int GetAtWidth() { if(this.at != null) return this.at.getWidth();return 0;}
    public final int GetAtHeight() { if(this.at != null) return this.at.getHeight();return 0;}
    public final int GetContainerWidth() { return this.width;}
    public final int GetContainerHeight() { return this.height;}
}



